import com.mysql.jdbc.jdbc2.optional.MysqlDataSource;

import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Scanner;

/**
 * Created with IntelliJ IDEA.
 * Description:
 * User: 马拉圈
 * Date: 2023-03-05
 * Time: 13:59
 */

public class Test {
    public static void main(String[] args)  throws SQLException {
        //创建并初始化数据源
        DataSource dataSource = new MysqlDataSource();
        ((MysqlDataSource)dataSource).setUrl("jdbc:mysql://127.0.0.1:3306/" +
                /*这里java107含义是数据库名*/"java107?characterEncoding=utf8&useSSL=false");
        //设置 url --  这个源的定位器~  大概就是这个操作可以获取到某个位置的数据库~
        // 这里必须有一个数据库，自动 use~~~，后续可以通过语句去变~


        ((MysqlDataSource)dataSource).setUser("root");
        // 设置 user -- 为根用户 ~  这样就有权限去操作了~

        ((MysqlDataSource)dataSource).setPassword("密码");
        //输入密码进入mysql~
        //这是你的mysql密码，错误是不能进入数据库的~



        Connection connection = dataSource.getConnection();
        //通过源构造连接器~ 与服务器进行初步联系~~~

        String sqlWords1 = "select * from classes";
        String sqlWords2 = "insert into classes (id, name) values(?, ?)";
        //一条语句自带分号执行时自带分号



        PreparedStatement preparedStatement = connection.prepareStatement(sqlWords1);
        PreparedStatement preparedStatement2 = connection.prepareStatement(sqlWords2);
        //连接器将一条语句转化为 ”准备状态“
        //有点像化学分子的活跃状态，被注入了化学反应所需要的活化能
        //一触即发~

        //preparedStatement.setString(1, "*");
        //控制所谓的【类通配符】（从左到右1 2 3 4~）






        //触发这个准备状态~-----------------------------------------------------------------------
        Scanner scanner = new Scanner(System.in);
        int inputId = scanner.nextInt();
        String inputName = scanner.nextLine();
        preparedStatement2.setInt(1, inputId);
        preparedStatement2.setString(2, inputName);
        int number = preparedStatement2.executeUpdate();//处理完成后再执行~

        System.out.println(number);
        //1. 返回值是被影响的行的个数~
        //查询语句用这个没有什么作用~并没有更新数据库的作用，返回的行数作用更是低下,所以查询语句的准备状态用这个方法执行会报错~
        //查询语句应该用executeQuery去
        //处理一下这个“准备状态”~



        ResultSet resultSet1 = preparedStatement.executeQuery();
        ResultSet resultSet2 = preparedStatement.executeQuery();

        //一跳语句的活跃状态，只能给出一个结果集，这里会强制将上面的结果集关闭释放



        //2. 这个准备状态的对象，调用特定函数，就可以直接作用于数据库了~

        // 两个操作都是触发了语句，也相当于语句在mysql中执行了~
        // 不过1. 只是普普通通的被影响的行的行数~，适用于【功能型的语句】~
        // 而 2. 它返回的是一个【结果集合】~，而这是功能型语句所不具备的~ ==>  本身就是个【迭代器】~
            // 因为查询语句不会对原数据进行影响，是个临时表~所以要在此程序中观察


        //resultSet.getInt("xxx");//获取那一行的某一具体列~
        //这一条会报错，这是因为 resultSet 这个引用 指向的是带头链表的哨兵罢了
        //即列表头~此节点并没有有效数据~


//        这个结果集并不是集合类~
//        while(resultSet1.next()) {
//            int id = resultSet1.getInt("id");
//            String name = resultSet1.getString("name");
//            System.out.println(id + " " + name);
//        }
//        已释放资源无法再次使用~


        //走下一步，如果不为空进入循环~ resultSet2 并不是链表的头指针~ 头指针在内部呢~ 每次走动都改变了此链表的性质~
        while(resultSet2.next()) {
            int id = resultSet2.getInt("id");
            String name = resultSet2.getString("name");
            System.out.println(id + " " + name);
        }
        System.out.println("--------------------------------------------------");


        //关闭释放资源 -----------  类似于吃完饭就走，否则提高服务器负担~~~
        resultSet1.close();//重复关闭没发生任何事
        resultSet2.close();
        preparedStatement.close();
        connection.close();
        //dataSource 不需要释放，因为这个只描述本机的数据源罢了~

    }
}